package main

import (
	"fmt"
	"strings"

	"github.com/astaxie/beego/orm"
)

// linkData 函数用于连接数据库
func InitMysql(data map[string]interface{}) ([]map[string]interface{}, error) {
	var lists []orm.ParamsList
	var tableMapList []map[string]interface{}
	fmt.Println("data:", data)
	_, datadb := linkData(data)
	num, err := datadb.Raw("SHOW TABLES").ValuesList(&lists)
	if err == nil && num > 0 {
		for i := 0; i < len(lists); i++ {
			var tableMap = make(map[string]interface{})
			var dataList []orm.ParamsList
			datadb.Raw("SHOW CREATE TABLE " + lists[i][0].(string)).ValuesList(&dataList)
			tableMap["table"] = lists[i][0]
			tableMap["value"] = lists[i][0]
			tableMap["label"] = lists[i][0]
			tableMap["key"] = i
			if strings.Contains(dataList[0][1].(string), "COMMENT=") {
				tableMap["label"] = tableMap["label"].(string) + "-" + strings.ReplaceAll(strings.Split(dataList[0][1].(string), "COMMENT=")[1], "'", "")
			}
			var fieldInfoList []orm.ParamsList
			datadb.Raw("SHOW FULL COLUMNS FROM " + lists[i][0].(string)).ValuesList(&fieldInfoList)
			var fieldInfoMapList []map[string]interface{}
			for n := 0; n < len(fieldInfoList); n++ {
				fieldInfoMap := make(map[string]interface{})
				fieldInfoMap["value"] = fieldInfoList[n][0]
				fieldInfoMap["label"] = fieldInfoList[n][0]
				fieldInfoMap["Field"] = fieldInfoList[n][0]
				fieldInfoMap["Type"] = fieldInfoList[n][1]
				fieldInfoMap["Null"] = fieldInfoList[n][3]
				fieldInfoMap["Comment"] = fieldInfoList[n][8]
				fieldInfoMapList = append(fieldInfoMapList, fieldInfoMap)
			}
			tableMap["fieldInfo"] = fieldInfoMapList
			tableMap["children"] = fieldInfoMapList
			tableMapList = append(tableMapList, tableMap)
		}
	} else {
		return nil, err
	}
	return tableMapList, nil
}

func InitPostgres(data map[string]interface{}) ([]map[string]interface{}, error) {
	var lists []orm.ParamsList
	var tableMapList []map[string]interface{}
	_, datadb := linkData(data)
	num, err := datadb.Raw("SELECT tablename as 'table', obj_description( tablename::text::regclass) AS tableName FROM pg_tables WHERE schemaname = 'public'").ValuesList(&lists)
	if err == nil && num > 0 {
		for i := 0; i < len(lists); i++ {
			var tableMap = make(map[string]interface{})
			var dataList []orm.ParamsList
			datadb.Raw("SHOW CREATE TABLE " + lists[i][0].(string)).ValuesList(&dataList)
			tableMap["table"] = lists[i][0]
			tableMap["value"] = lists[i][0]
			if lists[i][1] != nil {
				tableMap["label"] = lists[i][0].(string) + "-" + lists[i][1].(string)
			} else {
				tableMap["label"] = lists[i][0]
			}
			tableMap["key"] = i
			var fieldInfoList []orm.ParamsList
			datadb.Raw("SELECT column_name,data_type,is_nullable,column_comment FROM information_schema.columns WHERE table_schema = 'public' and table_name = " + lists[i][0].(string)).ValuesList(&fieldInfoList)
			var fieldInfoMapList []map[string]interface{}
			for n := 0; n < len(fieldInfoList); n++ {
				fieldInfoMap := make(map[string]interface{})
				fieldInfoMap["value"] = fieldInfoList[n][0]
				fieldInfoMap["label"] = fieldInfoList[n][0]
				fieldInfoMap["Field"] = fieldInfoList[n][0]
				fieldInfoMap["Type"] = fieldInfoList[n][1]
				fieldInfoMap["Null"] = fieldInfoList[n][2]
				fieldInfoMap["Comment"] = fieldInfoList[n][3]
				fieldInfoMapList = append(fieldInfoMapList, fieldInfoMap)
			}
			tableMap["fieldInfo"] = fieldInfoMapList
			tableMap["children"] = fieldInfoMapList
			tableMapList = append(tableMapList, tableMap)
		}
	} else {
		return nil, err
	}
	return tableMapList, nil
}

func InitOracle(data map[string]interface{}) ([]map[string]interface{}, error) {
	var lists []orm.ParamsList
	var tableMapList []map[string]interface{}
	_, datadb := linkData(data)
	num, err := datadb.Raw("SELECT tablename as 'table', obj_description( tablename::text::regclass) AS tableName FROM pg_tables WHERE schemaname = 'public'").ValuesList(&lists)
	if err == nil && num > 0 {
		for i := 0; i < len(lists); i++ {
			var tableMap = make(map[string]interface{})
			var dataList []orm.ParamsList
			datadb.Raw("SHOW CREATE TABLE " + lists[i][0].(string)).ValuesList(&dataList)
			tableMap["table"] = lists[i][0]
			tableMap["value"] = lists[i][0]
			if lists[i][1] != nil {
				tableMap["label"] = lists[i][0].(string) + "-" + lists[i][1].(string)
			} else {
				tableMap["label"] = lists[i][0]
			}
			tableMap["key"] = i
			var fieldInfoList []orm.ParamsList
			datadb.Raw("SELECT column_name,data_type,is_nullable,column_comment FROM information_schema.columns WHERE table_schema = 'public' and table_name = " + lists[i][0].(string)).ValuesList(&fieldInfoList)
			var fieldInfoMapList []map[string]interface{}
			for n := 0; n < len(fieldInfoList); n++ {
				fieldInfoMap := make(map[string]interface{})
				fieldInfoMap["value"] = fieldInfoList[n][0]
				fieldInfoMap["label"] = fieldInfoList[n][0]
				fieldInfoMap["Field"] = fieldInfoList[n][0]
				fieldInfoMap["Type"] = fieldInfoList[n][1]
				fieldInfoMap["Null"] = fieldInfoList[n][2]
				fieldInfoMap["Comment"] = fieldInfoList[n][3]
				fieldInfoMapList = append(fieldInfoMapList, fieldInfoMap)
			}
			tableMap["fieldInfo"] = fieldInfoMapList
			tableMap["children"] = fieldInfoMapList
			tableMapList = append(tableMapList, tableMap)
		}
	} else {
		return nil, err
	}
	return tableMapList, nil
}

// DSN=HiveDSN;UID=your_username;PWD=your_password
func dataUrl(data map[string]interface{}) map[string]interface{} {
	if data["dataType"] == "mysql" {
		data["dataUrl"] = data["user"].(string) + ":" + data["password"].(string) + "@tcp(" + data["host"].(string) + ":" + data["port"].(string) + ")/" + data["dbname"].(string) + "?charset=utf8mb4&parseTime=True&loc=Local"
	} else if data["dataType"] == "postgres" {
		data["dataUrl"] = "user=" + data["user"].(string) + " password=" + data["password"].(string) + " host=" + data["host"].(string) + " port=" + data["port"].(string) + " dbname=" + data["dbname"].(string) + " sslmode=disable"
	} else if data["dataType"] == "oracle" {
		data["dataUrl"] = "oracle://" + data["user"].(string) + ":" + data["password"].(string) + "@" + data["host"].(string) + ":" + data["port"].(string) + "/" + data["dbname"].(string) + "?charset=utf8"
	}
	return data
}
